package com.canaan.business.service.basic.impl;

import cn.hutool.core.collection.CollectionUtil;
import com.canaan.business.domain.basic.*;
import com.canaan.business.mapper.basic.WmsStorehouseAreaMapper;
import com.canaan.business.service.basic.*;
import com.canaan.common.exception.ServiceException;
import com.canaan.common.utils.DateUtils;
import com.canaan.common.utils.SecurityUtils;
import com.canaan.common.utils.StringUtils;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 库区Service业务层处理
 *
 * @author ruoyi
 * @date 2022-11-29
 */
@Service
public class WmsStorehouseAreaServiceImpl implements IWmsStorehouseAreaService
{
    @Resource
    private WmsStorehouseAreaMapper wmsStorehouseAreaMapper;
    @Resource
    private IWmsStorehouseService wmsStorehouseService;
    @Resource
    private IWmsStorehouseLocationService wmsStorehouseLocationService;
    @Resource
    private IStorehouseAreaShipperService storehouseAreaShipperService;
    @Resource
    private IStorehouseAreaPickerService storehouseAreaPickerService;

    /**
     * 查询库区
     *
     * @param id 库区主键
     * @return 库区
     */
    @Override
    public WmsStorehouseArea selectWmsStorehouseAreaById(Long id) {
        WmsStorehouseArea returnEntity = wmsStorehouseAreaMapper.selectWmsStorehouseAreaById(id);
        // 查询拣货员和码货员
        StorehouseAreaShipper searchShipper = new StorehouseAreaShipper();
        searchShipper.setStorehouseArea(returnEntity.getNo());
        List<StorehouseAreaShipper> storehouseAreaShipperList = this.storehouseAreaShipperService.selectStorehouseAreaShipperList(searchShipper);
        StorehouseAreaPicker searchPicker = new StorehouseAreaPicker();
        searchPicker.setStorehouseArea(returnEntity.getNo());
        List<StorehouseAreaPicker> storehouseAreaPickerList = this.storehouseAreaPickerService.selectStorehouseAreaPickerList(searchPicker);
        returnEntity.setAreaShipperList(storehouseAreaShipperList);
        returnEntity.setAreaPickerList(storehouseAreaPickerList);
        return returnEntity;
    }

    /**
     * 查询库区列表
     *
     * @param wmsStorehouseArea 库区
     * @return 库区
     */
    @Override
    public List<WmsStorehouseArea> selectWmsStorehouseAreaList(WmsStorehouseArea wmsStorehouseArea)
    {
        return wmsStorehouseAreaMapper.selectWmsStorehouseAreaList(wmsStorehouseArea);
    }

    /**
     * 新增库区
     *
     * @param entity 库区
     * @return 结果
     */
    @Override
    public WmsStorehouseArea insertWmsStorehouseArea(WmsStorehouseArea entity)
    {
        if(entity == null || entity.getNo() == null){
            throw new ServiceException("缺少库区编号");
        }else if(entity.getName() == null){
            throw new ServiceException("缺少库区名称");
        }
        List<String> nos = new ArrayList<>();
        nos.add(entity.getNo());
        List<String> names = new ArrayList<>();
        names.add(entity.getName());
        List<WmsStorehouseArea> repeatList = wmsStorehouseAreaMapper.listByNoOrName(nos, names);
        if(!repeatList.isEmpty()){
            //有重复的数据
            WmsStorehouseArea old = repeatList.stream()
                    .filter(e -> e.getNo().equals(entity.getNo())).findFirst().orElse(null);
            throw new ServiceException(old != null ? "库区编号已存在" : "库区名称已存在");
        }

        entity.setCreateBy(SecurityUtils.getUsername());
        entity.setCreateTime(DateUtils.getNowDate());
        wmsStorehouseAreaMapper.insertWmsStorehouseArea(entity);
        // 如果有码货员，添加码货员到表中
        if (CollectionUtil.isNotEmpty(entity.getAreaShipperList())){
            for (StorehouseAreaShipper storehouseAreaShipper : entity.getAreaShipperList()) {
                storehouseAreaShipper.setStorehouseArea(entity.getNo());
            }
            this.storehouseAreaShipperService.batchInsertStorehouseAreaShipper(entity.getAreaShipperList());
        }
        // 如果有拣货员，添加拣货员到表中
        if (CollectionUtil.isNotEmpty(entity.getAreaPickerList())){
            for (StorehouseAreaPicker storehouseAreaPicker : entity.getAreaPickerList()) {
                storehouseAreaPicker.setStorehouseArea(entity.getNo());
            }
            this.storehouseAreaPickerService.batchInsertStorehouseAreaPicker(entity.getAreaPickerList());
        }
        return entity;
    }

    /**
     * 修改库区
     *
     * @param entity 库区
     * @return 结果
     */
    @Override
    public int updateWmsStorehouseArea(WmsStorehouseArea entity)
    {
        //库区名称校验
        List<String> names = Collections.singletonList(entity.getName());
        List<WmsStorehouseArea> repeatList = wmsStorehouseAreaMapper.listByNoOrName(null, names);
        repeatList = repeatList.stream().filter(e -> !e.getId().equals(entity.getId())).collect(Collectors.toList());
        if(!repeatList.isEmpty()){
            //有重复的数据
            throw new ServiceException("库区名称已存在");
        }
        entity.setUpdateBy(SecurityUtils.getUsername());
        entity.setUpdateTime(DateUtils.getNowDate());
        this.storehouseAreaShipperService.deleteStorehouseAreaShipperByAreaNo(entity.getNo());
        this.storehouseAreaPickerService.deleteStorehouseAreaPickerByAreaNo(entity.getNo());
        // 如果有码货员，添加码货员到表中
        if (CollectionUtil.isNotEmpty(entity.getAreaShipperList())){
            for (StorehouseAreaShipper storehouseAreaShipper : entity.getAreaShipperList()) {
                storehouseAreaShipper.setStorehouseArea(entity.getNo());
            }
            this.storehouseAreaShipperService.batchInsertStorehouseAreaShipper(entity.getAreaShipperList());
        }
        // 如果有拣货员，添加拣货员到表中
        if (CollectionUtil.isNotEmpty(entity.getAreaPickerList())){
            for (StorehouseAreaPicker storehouseAreaPicker : entity.getAreaPickerList()) {
                storehouseAreaPicker.setStorehouseArea(entity.getNo());
            }
            this.storehouseAreaPickerService.batchInsertStorehouseAreaPicker(entity.getAreaPickerList());
        }
        return wmsStorehouseAreaMapper.updateWmsStorehouseArea(entity);
    }

    /**
     * 批量删除库区
     *
     * @param ids 需要删除的库区主键
     * @return 结果
     */
    @Override
    public int deleteWmsStorehouseAreaByIds(Long[] ids)
    {
        List<WmsStorehouseArea> list = wmsStorehouseAreaMapper.listByIds(Arrays.asList(ids));
        if(!list.isEmpty()){
            List<String> nos = list.stream().map(WmsStorehouseArea::getNo).collect(Collectors.toList());
            for (String no : nos) {
                // 删除拣货员、码货员
                this.storehouseAreaShipperService.deleteStorehouseAreaShipperByAreaNo(no);
                this.storehouseAreaPickerService.deleteStorehouseAreaPickerByAreaNo(no);
            }
            List<WmsStorehouseLocation> locationList = wmsStorehouseLocationService.listByAreaNos(nos);
            if(!locationList.isEmpty()){
                throw new ServiceException("库区下还存在库位，请先清除库位");
            }
        }

        return wmsStorehouseAreaMapper.deleteWmsStorehouseAreaByIds(ids);
    }

    /**
     * 删除库区信息
     *
     * @param id 库区主键
     * @return 结果
     */
    @Override
    public int deleteWmsStorehouseAreaById(Long id)
    {
        WmsStorehouseArea entity = this.selectWmsStorehouseAreaById(id);
        // 删除拣货员、码货员
        this.storehouseAreaShipperService.deleteStorehouseAreaShipperByAreaNo(entity.getNo());
        this.storehouseAreaPickerService.deleteStorehouseAreaPickerByAreaNo(entity.getNo());
        return wmsStorehouseAreaMapper.deleteWmsStorehouseAreaById(id);
    }

    /**
     * 根据编号或名称查询出列表
     * @param nos 编号列表
     * @param names 名称列表
     * @return 数据列表
     */
    @Override
    public List<WmsStorehouseArea> listByNoOrName(List<String> nos, List<String> names){
        return wmsStorehouseAreaMapper.listByNoOrName(nos,names);
    }

    /**
     * 导入数据
     * @param list 导入数据列表
     * @return 错误列表
     */
    @Override
    public List<String> importExcel(List<WmsStorehouseArea> list) {
        List<String> errorList = new ArrayList<>();
        if(StringUtils.isEmpty(list)){
            return errorList;
        }

        List<String> nos = list.stream().filter(e -> e.getNo() != null).map(WmsStorehouseArea::getNo).collect(Collectors.toList());
        List<String> names = list.stream().filter(e -> e.getName() != null).map(WmsStorehouseArea::getName).collect(Collectors.toList());
        List<String> storehouseNos = list.stream()
                .filter(e -> e.getStorehouseNo() != null).map(WmsStorehouseArea::getStorehouseNo).collect(Collectors.toList());

        //获取重复的数据
        List<WmsStorehouseArea> oldList = listByNoOrName(nos, names);
        nos = oldList.stream().map(WmsStorehouseArea::getNo).collect(Collectors.toList());
        names = oldList.stream().map(WmsStorehouseArea::getName).collect(Collectors.toList());

        //获取仓库列表
        Map<String, WmsStorehouse> storehouseMap = wmsStorehouseService.listByNoOrName(storehouseNos, null).stream()
                    .collect(Collectors.toMap(WmsStorehouse::getNo, e -> e));
        //行数据校验
        for (int i = 0; i < list.size(); i++) {
            WmsStorehouseArea entity = list.get(i);

            if(StringUtils.isEmpty(entity.getNo())){
                errorList.add("第" + ( i + 1 ) + "行缺少库区编号");
            }else if(nos.contains(entity.getNo())){
                errorList.add("第" + ( i + 1 ) + "行库区编号已存在");
            }

            if(StringUtils.isEmpty(entity.getName())){
                errorList.add("第" + ( i + 1 ) + "行缺少库区名称");
            }else if(names.contains(entity.getName())){
                errorList.add("第" + ( i + 1 ) + "行库区名称已存在");
            }

            if(!storehouseMap.containsKey(entity.getStorehouseNo())){
                errorList.add("第" + ( i + 1 ) + "行仓库编号不存在");
            }else{
                entity.setStorehouseName(storehouseMap.get(entity.getStorehouseNo()).getName());
            }

            if(StringUtils.isEmpty(entity.getStatus())){
                entity.setStatus("0");
            }
        }

        if(errorList.size() > 0){
            return errorList;
        }
        //没有什么问题就保存数据
        String username = SecurityUtils.getUsername();
        Date createTime = new Date();
        for (WmsStorehouseArea wmsStorehouseArea : list) {
            wmsStorehouseArea.setCreateBy(username);
            wmsStorehouseArea.setCreateTime(createTime);
            wmsStorehouseArea.setUpdateBy(null);
            wmsStorehouseArea.setUpdateTime(null);
            wmsStorehouseAreaMapper.insertWmsStorehouseArea(wmsStorehouseArea);
        }

        return errorList;
    }

    @Override
    public WmsStorehouseArea selectWmsStorehouseAreaByNo(String no) {
        WmsStorehouseArea area = wmsStorehouseAreaMapper.selectWmsStorehouseAreaByNo(no);
        return area;
    }

    /**
     * 根据仓库编号查询仓库列表
     *
     * @param storehouseNos 仓库编号列表
     * @return 仓库集合
     */
    @Override
    public List<WmsStorehouseArea> listByStorehouseNos(List<String> storehouseNos)
    {
        return wmsStorehouseAreaMapper.listByStorehouseNos(storehouseNos);
    }
}
